﻿using System;
using System.Collections.Generic;
using System.Text;

namespace 抽象类测试
{
    //www.cnblogs.com/wangfang224120999/archive/2008/12/19/1355940.html
    #region 抽象类ren
    abstract class Rena
    {
        //定义了一个只写的抽象的信仰Belief属性，只有set访问器
        abstract public string Belief
        {
            set;
        }
        //定义一个抽象的Eat方法
        abstract public void Eat();
    }
    class Chinese : Rena
    {
        //定义一个食物字段。
        string Foot;
        //定义一个标志，当给属性Belief赋值错误时，调用Eat方法时提示错误。
        bool bz = true;
        //定义一个信仰字段
        string belief;
        //用override关键字来覆写抽象类Ren的属性，同时给实现本类的信仰字段。
        public override string Belief
        {
            //使用set访问器，判断输入的信仰的类型，同时给食物字段赋值，
            //当用户输入不正确的信仰时，标志为False，提示错误。
            set
            {
                switch (value)
                {
                    case "佛教":
                        belief = value;
                        Foot = "忌荤食";
                        break;
                    case "伊斯兰教":
                        belief = value;
                        Foot = "忌猪肉";
                        break;
                    case "其他":
                        belief = value;
                        Foot = "无忌口";
                        break;
                    default:
                        Console.WriteLine("信仰应填写：佛教、伊斯兰教或其他");
                        bz = false;
                        break;
                }
            }
        }
        public override void Eat()
        {
            if (bz == true)
                Console.WriteLine("我们信仰是{0}，所以我们选择食物{1}", belief, Foot);
            else
                Console.WriteLine("操作失败！");
        }
    }
    #endregion

    #region 接口ITwoNumc
    interface ITwoNum
    {
        //定义了一个带两个引用型参数的无返回值方法，
        //不许加public修饰符。
        void twonum(ref int a, ref  int b);
    }
    class PF : ITwoNum
    {
        //定义了一个对参数进行平方的方法，实现了接口中的方法
        //实现接口的覆写方法时，可以不使用override
        public void twonum(ref int a, ref int b)
        {
            a = a * a;
            b = b * b;
        }
    }
    //JH类继承了接口
    class JH : ITwoNum
    {
        //定义了一个对参数进行值交换的方法，实现了接口中的方法
        //实现接口的覆写方法时，可以不使用override
        public void twonum(ref int a, ref int b)
        {
            int c = 0;
            c = a;
            a = b;
            b = c;
        }
    }
    #endregion

    #region IA IB 多接口
    interface IA
    {
        void Method();
    }
    interface IB
    {
        void Method();
    }
    //使用多重接口同名实现
    class C : IA, IB
    {
        //对于明确指定接口的成员，不需要加修饰符
        //这些成员被默认为public
        void IA.Method()
        {
            Console.WriteLine("我是接口IA中的方法");
        }
        //此时不做注明的将视为从另一个接口中继承来的方法
        public void Method()
        {
            Console.WriteLine("我是接口IB中的方法");
        }
    }
    #endregion

    #region Iflay ISay
    interface Iflay
    {
        //定义了canflay的方法，所以能飞的都可以继承
        //比如飞机、鸟、飞碟
        void canflay();
    }
    //定义了接口ISay
    interface ISay
    {
        //定义了cansay的方法，所以能说话的都可以继承
        //比如电视、mp3、会说话的鹦鹉
        void cansay();
    }
    //定义了一个动物的抽象类
    abstract class Animal
    {
        //定义了一个吃东西的方法
        abstract public void eat();
    }
    //定义了一个人类，继承了抽象动物类和接口isay，
    abstract class Ren : Animal, ISay
    {
        //继承接口的子类必须完全实现接口中的成员
        //实现了接口Isay中能说话的方法
        public void cansay()
        {
            Console.WriteLine("我是 【class Ren】 ，我继承了接口Isay,我能说话");
        }
        //再次定义一个保护的方法
        abstract public void protect();
    }
    //定义一个动漫人物类，继承了抽象Ren类和接口Iflay
    class DMren : Ren, Iflay
    {
        //定义类中的两个字段name、foot，提供给类中的方法
        string name;
        string foot;
        //定义构造函数，其中有两个参数，第一个的名字DMname，第二个是同名的foot
        //在构造函数中调用下面本类中的三个方法，和基类中的cansay方法。
        //创建构造函数就是为了在其他类中，创建对象时，无需在其他类中使用DMren类的对象调用的麻烦，可以一次性使用构造方法中的所有方法成员，
        //给字段赋值使用到了this关键字，因为是同名变量。
        public DMren(string DMname, string foot)
        {
            this.foot = foot;
            name = DMname;
            canflay();
            eat();
            protect();
            cansay();
        }
        public void canflay()
        {
            Console.WriteLine("我继承了接口Iflay，我是{0},我能飞", name);
        }
        //使用override关键字重写抽象类中的abstract修饰的eat方法
        public override void eat()
        {
            Console.WriteLine("我是继承了抽象类animal，我吃" + foot);
        }
        //使用override关键字重写抽象类中的abstract修饰的Protect方法
        public override void protect()
        {
            Console.WriteLine("我是继承了抽象类Ren,我能保护周围的人");
        }
    }
    //定义了一个鸟类，继承了动物抽象类和接口Iflay
    class bird : Animal, Iflay
    {
        string name;
        string foot;
        //如动漫DMren类一样使用构造方法，在创建对象的同时，一次性调用类中的所有要执行的方法和赋值
        public bird(string DMname, string foot)
        {
            this.foot = foot;
            name = DMname;
            canflay();
            eat();
        }
        public override void eat()
        {
            Console.WriteLine("我是继承了抽象类animal，我吃" + foot);
        }
        public void canflay()
        {
            Console.WriteLine("我继承了接口Iflay，我是{0},我能飞", name);
        }
    }
    #endregion

    #region 泛型测试1   
    /// < summary>  
    /// 定义一个泛型类，该类有两个类型参数，分别是T,S  
    /// http://pw.cnblogs.com  
    /// < /summary>  
    /// < typeparam name="T">类型参数< /typeparam>  
    /// < typeparam name="S">类型参数< /typeparam>  
    public class Test<XXX, S11>
    {
        //泛型类的类型参数可用于类成员  
        private XXX name;
        private S11 age;

        public Test(XXX Name, S11 Age)
        {
            this.name = Name;
            this.age = Age;
        }

        public void SetValue()
        {
            Console.WriteLine(name.ToString());
            Console.WriteLine(age.ToString());
        }
    }  
    #endregion
}
